<!--瀑布图-->

<template>
  <div class="w-h-full">
    <!--组件遮罩层，用于在设计器中显示-->
    <div v-if="shade" class="shade"></div>

    <div v-resize="resizeHandle" style="width: 100%; height: 100%;">
      <div :id="'chart-'+component.id+'-'+chartDomNum" class="w-h-full"></div>
    </div>
  </div>
</template>

<script>

  import FuncCompMixin from '@/mixin/FuncCompMixin'
  import ChartCompMixin from '@/mixin/ChartCompMixin'
  import PnDesigner from '@/utils/PnDesigner'

  const _this = {
    name: 'WaterfallPlotChart', // 此名称必须填写，且必须与组件文件名相同
    mixins: [FuncCompMixin, ChartCompMixin],
    attr: {
      version: '1.2',
      configDataTemp: Object.assign({

        // 组件相关配置属性，Echarts图表组件的相关配置属性，必须在chartOption对象下定义
        chartOption: {
          pn_chart_type: 'echarts-gl',
          title: PnDesigner.buildTitleConfigData(),
          tooltip: PnDesigner.buildTooltipConfigData({
            trigger: 'item',
            axisPointer: {
              type: 'shadow'
            }
          }),
          legend: PnDesigner.buildLegendConfigData({
            useSystemLegend: true,
            systemLegendData: {
              positive: "上升",
              minus: "下降",
              total: "总计"
            }
          }),
          grid: PnDesigner.buildGridConfigData(),
          xAxis: PnDesigner.buildXAxisConfigData(),
          yAxis: PnDesigner.buildYAxisConfigData(),
          series: {
            showTotal: true,
            positiveColor: '#2196f3',
            minusColor: '#f44336',
            totalColor: '#9e9e9e',
            label: {
              show: true,
              fontSize: 10,
              color: '#fff'
            }
          }
        }

      }, PnDesigner.buildFuncCompDatasourceField({ // 如果组件需要配置数据源，则需要调用此函数构建数据源字段对象
        ds_resultObjTemplate: [
          {
            field: 'name',
            remark: '类目'
          },
          {
            field: 'value',
            remark: '值'
          }
        ],
        ds_resultObj: [
          {
            name: '周一',
            value: 300
          },
          {
            name: '周二',
            value: 900
          },
          {
            name: '周三',
            value: 200
          },
          {
            name: '周四',
            value: 350
          },
          {
            name: '周五',
            value: 1200
          },
          {
            name: '周六',
            value: 800
          },
          {
            name: '周日',
            value: -1500
          }
        ],
        ds_useFilter: true, // 是否使用过滤器，默认不使用
        ds_useTimer: true, // 是否开启定时器配置，默认不开启
      }), PnDesigner.buildFuncCompGlobalField(), PnDesigner.buildEchartCompCustomOption(), PnDesigner.buildFuncCompInteractionConfiguration([
        PnDesigner.buildFuncCompInteractionStreamItem('itemClick', [
          PnDesigner.buildFuncCompInteractionFieldsMapItem('name','','类目'),
          PnDesigner.buildFuncCompInteractionFieldsMapItem('value','','值')
        ])
      ]))
    },
    data() {
      return {}
    },
    mounted() {
      this.init();

      this.setTimer(() => { //定时器，如果当前组件不使用定时器，可以将此段代码删除
        this.init()
      })
    },
    methods: {
      init () { // 组价初始化函数，函数名必须使用init，不可更改
        this.initDatasource(() => {
          this.chart.setOption(this.chartOption);
          this.runCustomGlobalJsCode();
          this.runDataItemClickJsCode(this.launchInteractionStream)
        }, (result) => {
          this.chart.setOption(this.chartOption);
          this.runCustomGlobalJsCode();
          this.runDataItemClickJsCode(this.launchInteractionStream)
        });
      },

      launchInteractionStream (params) {
        this.$PnDesigner.launchInteractionStream(this.component.compConfigData, 'itemClick', {
          name: params.seriesName,
          value: params.data.value[0]
        })
      },

      getSeries (data, renderItem) {
        let sum = 0;
        let series = [];
        data.forEach((item, index) => {
          sum += item.value;
          let temp = {
            type: 'custom',
            name: item.name,
            renderItem: renderItem,
            label: {
              show: this.component.compConfigData.chartOption.series.label.show,
              fontSize: this.component.compConfigData.chartOption.series.label.fontSize,
              color: this.component.compConfigData.chartOption.series.label.color,
              formatter: (params) => {
                return params.value[0];
              }
            },
            data: [{value: [item.value, sum]}],
          }
          // 总计配置
          if (index == data.length - 1) {
            temp.color = this.component.compConfigData.chartOption.series.totalColor
            temp.id = 'total';
            temp.data[0].value[1] = temp.data[0].value[0];
            temp.data[0].value.push(data[0].value);
          }
          if (item.value < 0) {
            temp.color = this.component.compConfigData.chartOption.series.minusColor
          }else if (item.value > 0 && index != data.length - 1) {
            temp.color = this.component.compConfigData.chartOption.series.positiveColor
          }
          if (this.component.compConfigData.chartOption.legend.useSystemLegend) {
            if (index == data.length - 1) {
              temp.name = this.component.compConfigData.chartOption.legend.systemLegendData.total;
            } else if (item.value < 0) {
              temp.name = this.component.compConfigData.chartOption.legend.systemLegendData.minus;
            } else {
              temp.name = this.component.compConfigData.chartOption.legend.systemLegendData.positive;
            }
          }
          series.push(temp);
        });

        return series;
      },

      renderItem (params, api) {
        let categoryIndex = params.seriesIndex;  // 类目轴的索引
        let width = api.size([0, 1])[0] * 0.6;   // 计算宽度

        // 计算 实际点
        let start = api.coord([categoryIndex, api.value(1)]);
        let end = api.coord([categoryIndex, 0]);

        let height = end[1] - start[1];
        let x = start[0] - width / 2;
        let y = start[1];

        let lineY;
        let startY;

        // 前一个点的坐标
        let perStart = api.coord([categoryIndex - 1, api.value(1) - api.value(0)]);
        let perEnd = api.coord([categoryIndex - 1, 0]);
        height = height - (perEnd[1] - perStart[1]);
        // 处理负值
        if (height < 0) {
          height = -height;
          y = y - height;
        }

        if (api.value(0) <= 0) {
          lineY = y + 0.5;
        } else {
          lineY = y + height - 0.5;
        }

        let rectShape = this.$Echarts.graphic.clipRectByRect({
          x, y, width, height,
        }, {
          x: params.coordSys.x,
          y: params.coordSys.y,
          width: params.coordSys.width,
          height: params.coordSys.height
        });
        return {
          type: 'rect',
          shape: rectShape,
          style: api.style(),
        };
      }
    },
    computed: {
      chartOption () {
        let legendOption = PnDesigner.buildLegendChartOption(this.component.compConfigData.chartOption.legend);
        delete legendOption.data

        let option = {
          title: PnDesigner.buildTitleChartOption(this.component.compConfigData.chartOption.title),
          grid: PnDesigner.buildGridConfigData(),
          xAxis: PnDesigner.buildXAxisChartOption(this.component.compConfigData.chartOption.xAxis),
          yAxis: PnDesigner.buildYAxisChartOption(this.component.compConfigData.chartOption.yAxis),
          tooltip: Object.assign(PnDesigner.buildTooltipChartOption(this.component.compConfigData.chartOption.tooltip), {
            formatter: (params) => {
              return params.seriesName + ": " + params.data.value[0];
            }
          }),
          legend: legendOption,
        };

        let data = this.$PnUtil.deepClone(this.runCustomFilter(this.component.compConfigData.ds_resultObj));
        let total = 0;
        data.forEach(item => {
          total += item.value
        })
        data.push({
          name: this.component.compConfigData.chartOption.legend.systemLegendData.total,
          value: total
        })

        option.series = this.getSeries(data, this.renderItem);
        option.xAxis.data = data.map(item => item.name);

        // 下面这一段代码用于合并组件的扩展配置，如果组件不需要扩展配置，可以删掉
        option = this.$PnDesigner.mergeChartCustomOption(option, this.component.compConfigData.customOption);

        return option;
      }
    }
  };

  export default _this
</script>

<style scoped>

</style>
